package com.yida.system.service.impl;

import java.util.List;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.yida.common.core.exception.ServiceException;
import com.yida.common.core.ukey.SM2SM3;
import com.yida.common.core.utils.DateUtils;
import com.yida.common.core.utils.StringUtils;
import com.yida.common.core.utils.uuid.IdUtils;
import com.yida.common.security.utils.SecurityUtils;
import com.yida.system.api.domain.SysUserUkey;
import com.yida.system.mapper.SysUserUkeyMapper;
import com.yida.system.service.ISysUserUkeyService;

import cn.hutool.core.util.RandomUtil;

/**
 * Ukey用户信息处理
 * 
 * @author hmh
 * @date 2023/04/17
 */
@Service
public class SysUserUkeyServiceImpl implements ISysUserUkeyService {

    private static final Logger log = LoggerFactory.getLogger(SysUserUkeyServiceImpl.class);

    @Autowired
    private SysUserUkeyMapper sysUserUkeyMapper;

    /* 
     * 获取绑定UKey信息
     */
    @Override
    public List<SysUserUkey> selectSysUserUkeyList(SysUserUkey sysUKeyUser) {
        // System.out.println("status:" + sysUKeyUser.getStatus());
        // System.out.println("area_id:" + sysUKeyUser.getAreaId());
        return sysUserUkeyMapper.selectSysUserUkeyListNoKeyInfo(sysUKeyUser);
    }

    /* 
     * 获取绑定key信息
     */
    @Override
    public SysUserUkey selectSysUserKeyInfo(Long userId) {
        return sysUserUkeyMapper.selectSysUserUkeyByUserId(userId, 0);
    }

    /**
     * 根据用户名获取对应的代签信息（包括pin和rnd待签串）给前端，由前端生成签名数据后，交由后端比对是否一致
     * 
     */
    @Override
    public SysUserUkey getWaitSignMsgByUserName(String userName, String ukeyId) {
        // 查询启用状态下的Ukey绑定信息
        SysUserUkey suu = sysUserUkeyMapper.selectSysUserUkeyByUserName(userName, 0);
        if (StringUtils.isNull(suu)) {
            throw new ServiceException("当前用户未绑定Ukey,请使用其他方式登录！");
        }
        if (!ukeyId.equals(suu.getUkeyId())) {
            throw new ServiceException("请确认当前Ukey是否为本人持有！");
        }
        // 获取绑定PIN码
        String pin = suu.getPin();
        // 生成6位随机码进行待签
        String rnd = RandomUtil.randomString(IdUtils.fastSimpleUUID(), 6);
        // 预留状态码
        return new SysUserUkey(pin, rnd);
    }

    /**
     * 检测待签串是否一致（校验前端传入待签串）
     */
    @Override
    public boolean checkSign(SysUserUkey sysUKeyUser) {
        // 获取对应信息
        SysUserUkey rSysUserUkey = sysUserUkeyMapper.selectSysUserUkeyByUserNameAndUkeyId(sysUKeyUser.getUserName(), sysUKeyUser.getUkeyId(), 0);
        if (StringUtils.isNull(rSysUserUkey)) {
            throw new ServiceException("[S]未获取到对应UKey信息，请确认当前设备是否本人持有，或未开启检测！");
        }
        if (!sysUKeyUser.getUkeyId().equals(rSysUserUkey.getUkeyId())) {
            throw new ServiceException("[S]Ukey信息与当前设备不符合，请确认当前设备是否本人持有！");
        }
        String signUkeyStr = sysUKeyUser.getSignUKeyStr();
        String rnd = sysUKeyUser.getRnd();
        // String pin = rSysUserUkey.getPin();
        String pubkeyx = rSysUserUkey.getPubKeyX();
        String pubkeyy = rSysUserUkey.getPubKeyY();
        // String userId = Long.toString(rSysUserUkey.getUserId());
        // return SM2SM3.YtVerfiy(userId, rnd, pubkeyx, pubkeyy, signUkeyStr);
        String userName = sysUKeyUser.getUserName();// 变更采用绑定的userName进行签名
        return SM2SM3.YtVerfiy(userName, rnd, pubkeyx, pubkeyy, signUkeyStr);
    }

    /* 
     * 根据UkeyId获取PIN码
     */
    @Override
    public String getPinByUKeyId(String UkeyId) {
        // TODO Auto-generated method stub
        return null;
    }

    /* 
     * 
     */
    @Override
    public String getPin() {
        String pin = "gwjkey";
        try {
            // 生成6位Pin码
            pin = RandomUtil.randomString(IdUtils.fastSimpleUUID(), 6);
        } catch (Exception e) {
            log.error("获取PIN异常", e);
        }
        return pin;
    }

    /* 
     * 绑定对应用户Ukey信息
     */
    @Override
    public int bindUkey(SysUserUkey sysUKeyUser) {
        // 获取前端传回数据进行绑定
        // 状态默认启动
        sysUKeyUser.setStatus(0);
        sysUKeyUser.setCreateBy(SecurityUtils.getUsername());
        sysUKeyUser.setCreateTime(DateUtils.getNowDate());
        return sysUserUkeyMapper.insertSysUserUkey(sysUKeyUser);
    }

    /* 
     * 根据用户ID进行UKey绑定
     */
    @Override
    public boolean bindUkeyByUserId(SysUserUkey sysUKeyUser) {
        // 判断是否存在绑定值
        SysUserUkey rSysUKeyUser = sysUserUkeyMapper.selectSysUserUkeyByUserId(sysUKeyUser.getUserId(), null);
        if (StringUtils.isNull(rSysUKeyUser)) {
            return bindUkey(sysUKeyUser) > 0;
        }
        // 存在则判断当前绑定状态
        if (0 == rSysUKeyUser.getStatus()) {
            throw new ServiceException("[S]当前用户UKey处于启用状态，请解绑后再处理！");
        }
        // 存在情况下，进行换绑 做数据更新
        return sysUserUkeyMapper.updateSysUserUkey(sysUKeyUser) > 0;
    }

    /* 
     * 解除对应用户Ukey信息
     */
    @Override
    public int unbindingUkey(SysUserUkey sysUKeyUser) {
        sysUKeyUser.setStatus(1);
        sysUKeyUser.setUpdateBy(SecurityUtils.getUsername());
        sysUKeyUser.setUpdateTime(DateUtils.getNowDate());
        return sysUserUkeyMapper.unbindingUkey(sysUKeyUser.getUserId());
    }

    /* 
     * 切换UKey状态
     */
    @Override
    public int changeUkeyStatus(SysUserUkey sysUKeyUser) {
        sysUKeyUser.setUpdateBy(SecurityUtils.getUsername());
        sysUKeyUser.setUpdateTime(DateUtils.getNowDate());
        return sysUserUkeyMapper.changeUkeyStatus(sysUKeyUser);
    }

    /* 
     * 删除用户绑定信息
     */
    @Override
    public int delUkeyInfo(Long userId) {
        return sysUserUkeyMapper.deleteSysUserUkeyByUserId(userId);
    }

    public static void main(String[] args) {
        // String userId = "22";
        String userId = "ss";
        String rnd = "76e35c";

        // {pin: "4ab563", rnd: "81128b"}
        String pubkeyx = "4F69EF262DB9A02CA90412A3684AA0AD91AD0613EF70C85B654C33ED5171CF29";
        String pubkeyy = "E37BEDC529361CE4A42B460CD3FEE0AB5BC5E0CBE90781560B3B3F290360D1CB";
        String signUkeyStr = "A8A481029A81B00048F6510200EA8102080000004CC7C33458BB8A02000000000F00000070C7C334DCF65102F05FC200FFFFFFFFE8F65102C5C2B000F8825201";
        boolean b = SM2SM3.YtVerfiy(userId, rnd, pubkeyx, pubkeyy, signUkeyStr);
        System.out.println(b);
    }

}
